#include "QtTutorialApp3.h"
#include <QPainter>

#ifdef WIN32
#ifdef QtTutorial3_EXPORTS
#define QTTUTORIAL3_API __declspec(dllexport)
#else
#define QTTUTORIAL3_API __declspec(dllimport)
#endif
#else
#define QTTUTORIAL3_API
#endif

extern "C" QTTUTORIAL3_API Blobz::QtBaseApplication* GetInstance()
{
	QtTutorial3::QtTutorial3App* pTutorial = new QtTutorial3::QtTutorial3App();
	return pTutorial;
}

extern "C" QTTUTORIAL3_API unsigned int GetMajorReleaseVersion()
{
	return NUI_RELEASE_MAJOR_VER;
}

extern "C" QTTUTORIAL3_API unsigned int GetMinorReleaseVersion()
{
	return NUI_RELEASE_MINOR_VER;
}

extern "C" QTTUTORIAL3_API bool IsQtApp()
{
	return true;
}

extern "C" QTTUTORIAL3_API const char* GetAppName()
{
	return "QtTutorial3";
}

namespace QtTutorial3
{
	/**
	* Constructor
	*/
	QtTutorial3App::QtTutorial3App():
			mMessage("Click the buttons to change the message"),
			mFont("Verdana", 18),
			mFontMetrics(mFont)
	{
		setFlags(QGraphicsItem::ItemIsFocusable);

		// Connect the size change signal to the handling method.
		connect(this, SIGNAL(maximizedChanged(bool)), SLOT(onItemsSizeSetup()));
	}

	/**
	* Destructor
	*/
	QtTutorial3App::~QtTutorial3App()
	{
	}

	/**
	* Loads the objects used in the app
	*/
	bool QtTutorial3App::onInitialize()
	{
		// Open a config file
		Blobz::Config config;
		config.load(getApplicationDirectory()+"settings.txt");

		InteractableQGraphicsItem::setInteractionLocked(true);

		// Loads the image
		bool success = mBackground.load(getApplicationDirectory()+"bg.png");

		// Parse the button names
		QStringList names;
		names << "PrevPage.png" << "Home.png" << "Refresh.png" << "NextPage.png" << "Keyboard.png";

		int buttonSize = 100;
		int buttonPosX = getWindowSize().width() / 2 - 250;
		int buttonPosY = 300;
		for(int i = 0;i < 5;++i)
		{
			Blobz::ButtonItem *item = new Blobz::ButtonItem(this);
			QString path = getApplicationDirectory()+"Icons/"+names.at(i);
			item->load(path,NULL,path,NULL);
			item->setPos(buttonPosX,buttonPosY);
			item->setSize(buttonSize,buttonSize);
			mButtons.push_back(item);

			buttonPosX += buttonSize;
		}

		// Connect the clicked signal of the buttons to get the click events
		connect(mButtons[0], SIGNAL(clicked()), this, SLOT(back()));
		connect(mButtons[1], SIGNAL(clicked()), this, SLOT(home()));
		connect(mButtons[2], SIGNAL(clicked()), this, SLOT(reload()));
		connect(mButtons[3], SIGNAL(clicked()), this, SLOT(forward()));
		connect(mButtons[4], SIGNAL(clicked()), this, SLOT(showKeyboard()));

		return success;
	}

	/**
	* Unload all objects
	*/
	void QtTutorial3App::onDeinitialize()
	{
	}

	/**
	* Triggered on every frame update
	* \param inFrameTime Time since last update ( in seconds )
	*/
	void QtTutorial3App::onUpdate( float inFrameTime )
	{

	}

	/**
	* Events handler
	* \param inEvent Consist of event information
	* \return bool
	*/
	bool QtTutorial3App::onEvent( QEvent *inEvent )
	{
		return false;
	}

	/**
	* Triggered when there is a finger down event on the screen
	* \param inData holds the touch information
	*/
	void QtTutorial3App::onFingerDown( const TouchListener::TouchData& inData )
	{
		QVector<Blobz::ButtonItem*>::iterator iter = mButtons.begin();
		for(;iter != mButtons.end();++iter)
		{
			(*iter)->onFingerDown(inData);
		}
	}

	/**
	* Triggered when there is a finger up event on the screen
	* \param inData holds the touch information
	*/
	void QtTutorial3App::onFingerUp( const TouchListener::TouchData& inData )
	{
		QVector<Blobz::ButtonItem*>::iterator iter = mButtons.begin();
		for(;iter != mButtons.end();++iter)
		{
			(*iter)->onFingerUp(inData);
		}
	}

	/**
	* Triggered when there is a finger update event on the screen
	* \param inData holds the touch information
	*/
	void QtTutorial3App::onFingerUpdate( const TouchListener::TouchData& inData )
	{
		QVector<Blobz::ButtonItem*>::iterator iter = mButtons.begin();
		for(;iter != mButtons.end();++iter)
		{
			(*iter)->onFingerUpdate(inData);
		}
	}

	/**
	* Triggered when there is a finger moves out of the screen or application window
	* \param inData holds the touch information
	*/
	void QtTutorial3App::onFingerExit( const TouchListener::TouchData& inData )
	{
		// just treat finger exit events as finger up events
		onFingerUp(inData);
	}

	/**
	* Render method
	* \param inpPainter QT Rendering system pointer
	* \param inpOption Pointer to various rendering options
	* \param inpWidget Pointer to Parent Widget
	*/
	void QtTutorial3App::paint( QPainter* inpPainter, const QStyleOptionGraphicsItem *inpOption, QWidget *inpWidget )
	{
		// Save window size for rendering.
		QSizeF windowSize = getWindowSize();

		// Render the background
		inpPainter->drawImage(QRectF(QPointF(0, 0), windowSize), mBackground); 

		// Render the message at the center of the screen
		inpPainter->setFont(mFont);
		inpPainter->setPen(Qt::black);
		QSize textSize = mFontMetrics.size(Qt::TextShowMnemonic, mMessage);
		QRectF rect(QPointF(), textSize);
		rect.moveTo(QPointF((windowSize.width() - textSize.width())/2, 250));
		inpPainter->drawText(rect, mMessage, QTextOption(Qt::AlignCenter));
	}

	/**
	* Slot for handling Back button Press event
	*/
	void QtTutorial3App::back()
	{
		mMessage = "Back button triggered";
	}

	/**
	* Slot for handling Home button Press event
	*/
	void QtTutorial3App::home()
	{
		mMessage = "Home button triggered";
	}

	/**
	* Slot for handling reload button Press event
	*/
	void QtTutorial3App::reload()
	{
		mMessage = "Reload button triggered";
	}

	/**
	* Slot for handling Forward button Press event
	*/
	void QtTutorial3App::forward()
	{
		mMessage = "Forward button triggered";
	}	

	/**
	* Slot for handling Keyboard button Press event
	*/
	void QtTutorial3App::showKeyboard()
	{
		mMessage = "Show keyboard triggered";
	}

	/**
	* Rescale and reposition items.
	*/
	void QtTutorial3App::onItemsSizeSetup()
	{
		// The scenes scale changes with the relative window size. When fullscreened it is 1.
		float naturalScale = scale();

		// The same values that were used to set up the program but resized.
		int buttonSize = 100 * naturalScale;
		int buttonPosX = getWindowSize().width() / 2 - 250 * naturalScale;
		int buttonPosY = 300 * naturalScale;

		// The buttons are scaled and repositioned.
		QVector<Blobz::ButtonItem*>::iterator iter = mButtons.begin();
		for(;iter != mButtons.end();++iter)
		{
			(*iter)->setScale(naturalScale);

			(*iter)->setPos(buttonPosX,buttonPosY);

			buttonPosX += buttonSize;
		}
	}
}
